Micron Document
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| SparkN0de-git | SparkN0de |
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------


Commit 450ed9e35490702052539e98baa04edaabf876e7


Parents : b80d22a
Author : Ivan <ivan@quad4.io>
Signature : Signature validation error
Date : 2026-04-25T16:29:54-05:00

feat(interfaceDiscoveryUtils): add parseRNodeFrequencyHz function for frequency conversion in API payloads

Changes

1 files changed, 54 insertions(+), 0 deletions(-)


Diff

diff --git a/meshchatx/src/frontend/js/interfaceDiscoveryUtils.js b/meshchatx/src/frontend/js/interfaceDiscoveryUtils.js
index 5bb7bd13..d31e6572 100644
--- a/meshchatx/src/frontend/js/interfaceDiscoveryUtils.js
+++ b/meshchatx/src/frontend/js/interfaceDiscoveryUtils.js
@@ -1,3 +1,57 @@
+/**
+ * RNode carrier frequency as integer Hz for API payloads (Reticulum stores Hz, not MHz decimals).
+ */
+export function parseRNodeFrequencyHz(value) {
+ if (value === null || value === undefined || value === "") {
+ return null;
+ }
+ if (typeof value === "number" && Number.isFinite(value)) {
+ let f = value;
+ if (f <= 0) {
+ return Math.round(f);
+ }
+ if (f >= 1_000_000) {
+ return Math.round(f);
+ }
+ const isInteger = Math.abs(f - Math.round(f)) < 1e-9;
+ if (!isInteger || (isInteger && f < 10_000)) {
+ f *= 1_000_000;
+ }
+ return Math.round(f);
+ }
+ let s = String(value).trim().toLowerCase().replace(/_/g, "");
+ let mult = 1;
+ const pairs = [
+ ["ghz", 1e9],
+ ["mhz", 1e6],
+ ["khz", 1e3],
+ ["hz", 1],
+ ];
+ for (const [suffix, m] of pairs) {
+ if (s.endsWith(suffix)) {
+ s = s.slice(0, -suffix.length).trim();
+ mult = m;
+ break;
+ }
+ }
+ const n = Number(s);
+ if (!Number.isFinite(n)) {
+ return null;
+ }
+ let f = n * mult;
+ if (f <= 0) {
+ return Math.round(f);
+ }
+ if (f >= 1_000_000) {
+ return Math.round(f);
+ }
+ const isInteger = Math.abs(f - Math.round(f)) < 1e-9;
+ if (!isInteger || (isInteger && f < 10_000)) {
+ f *= 1_000_000;
+ }
+ return Math.round(f);
+}
+
/**
* Coordinates and optional discovery numerics: empty or invalid means "not set" (Reticulum treats omission as optional).
*/


──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────